<?php
namespace app\common\validate\jy;

class Order extends Base {
	/**
     * 验证规则
     */
    protected $rule = [
    	'lock'         => 'require',
        'id'           => 'require|isUser:jy\\Order',
        'uid'          => 'require',
        'spreadid'     => 'spreadid',
        'aid'          => 'require:aid_require|isUser:tyyh\\UserAddress',
        'ids'          => 'require|isUsers:jy\\Order',
        'cids'         => 'require|hasCid|isUsers:tyyh\\UserCart|storesNum|stores|productsInStroe|products|productSpecs',
        'sid'          => 'require|isShow:tysj\\Store',
        'pid'          => 'require|isBuy',
        'psid'         => 'require|psid',
        'balance'      => 'excess',
        'num'          => 'require|integer|gt:0|minBuy|num',
        'fee'          => 'require|fee',
        'tracking'     => 'max:100',
        'out_trade_no' => 'require',
        'take_type'    => 'require|isOptions:TakeType'
    ];
    /**
     * 提示消息
     */
    protected $message = [
    	'lock.require'             => '验证规则场景不存在',
        'id.require'               => '订单ID不能为空',
        'id.isUser'                => '订单不属于您',
        'id.isSetAddress'          => '订单已经发货无法修改地址',
        'id.reverse'               => '订单不是待支付状态',
        'id.isRefund'              => '该订单不处于可退款状态',
        'id.isStoreOrder'          => '订单不属于您',
        'uid.require'              => 'uid不能为空',
        'uid.sendStatus'           => '订单不处于待发货状态',
        'uid.isStoreOrder'         => '订单不属于您的店铺',
        'uid.harvest'              => '您没有收货权限',
        'aid.require'              => '请选择收货地址',
        'aid.isUser'               => '地址不属于您',
    	'ids.require'              => '请选择地址',
        'ids.isUsers'              => '订单ID不属于您',
        'sid.require'              => '店铺ID不能为空',
        'sid.isShow'               => '店铺未开业',
        'pid.require'              => '产品ID不能为空',
        'pid.isBuy'                => '产品暂未上线',
        'psid.require'             => '产品规格ID不能为空',
        'psid.psid'                => '产品规格不存在',
        'balance.excess'           => '余额不足',
        'num.require'              => '购买数量不能为空',
        'num.integer'              => '购买数量必须是一个整数',
        'num.gt'                   => '购买数量必须大于0',
        'num.minBuy'               => '购买数量应大于最小购买数',
        'num.num'                  => '库存不足',
        'cids.require'             => '购物车ID不能为空',
        'cids.hasCid'              => '购物车ID不存在',
        'cids.isUsers'             => '购物车ID不属于您',
        'cids.storesNum'           => '一笔订单只能购买一家店的商品',
        'cids.stores'              => '店铺已经闭店',
        'cids.productsInStroe'     => '产品已经移除',
        'cids.products'            => '产品已经下架',
        'cids.productSpecs.nexus'  => '已经被产品移除',
        'cids.productSpecs.num'    => '库存不足',
        'cids.productSpecs.minBuy' => '购买数量不足',
        'fee.require'              => '退款金额不能为空',
        'fee.fee'                  => '可退款金额不足',
        'tracking.require'         => '快递单号不能为空',
        'tracking.max'             => '快递单号不能超过100个字符',
        'out_trade_no.require'     => '订单编号不能为空',
        'take_type.require'        => '提货方式不能为空',
        'take_type.isOptions'      => '提货方式不合法',
        'spreadid.spreadid'        => '推广用户不合法'
    ];
    /**
     * 验证场景
     */
    protected $scene = [
        'save'         => ['uid', 'sid' => 'require|unique:app\common\model\tysj\BusinessLicense|isUser:tysj\Store', 'photo', 'code', 'merchant', 'corporation'],
        'look'         => ['sid' => 'require|isShow:tysj\\Store'],
        'info'         => ['uid' => 'require|isUser:ty\\order'],
        'create'       => ['pid', 'aid', 'psid', 'num', 'spreadid', 'take_type', 'balance'],
        'cart'         => ['cids','aid', 'spreadid', 'take_type', 'balance'],
        'private'      => ['uid'],
        'preview'      => ['id', 'uid'],
        'send_product' => ['id' => 'require', 'uid' => 'require|sendStatus|isStoreOrder', 'tracking'],
        'harvest'      => ['id', 'uid' => 'require|harvest'],
        'set_address'  => [
            'id' => 'require|isUser:jy\\Order|isSetAddress',
            'aid'
        ],
        'reverse'      => [
            'id' => 'require|isUser:jy\\Order|reverse'
        ],
        'refund'       => [
            'id' => 'require|isUser:jy\\Order|isRefund',
            'uid',
            'fee'
        ],
        'store'        => [
            'id' => 'require|isStoreOrder'
        ],
        'preview_look4out_trade_no'  => [
            'out_trade_no'
        ]
    ];

    //店铺ID
    protected function isBuy($value, $rule, $data = []) {
        $productValidate = loadValidate('tysj\\Product');
        return $productValidate->scene('buy')->check(['id' => $value]);
    }

    //店铺规格
    protected function psid($value, $rule, $data = []) {
        return !!loadModel('tysj\\ProductSpecsNexus')->where(['pid' => $data['pid'], 'psid' => $value])->count();
    }

    //最小购买数
    protected function minBuy($value, $rule, $data = []) {
        $data = loadOnly('Model')->lockFind('tysj\\ProductSpecs', $data['psid']);
        return $data['min_purchase_quantity'] <= $value;
    }

    //检查库存是否够用
    protected function num($value, $rule, $data = []) {
        $data = loadOnly('Model')->lockFind('tysj\\ProductSpecs', $data['psid']);
        return $data['inventory'] >= $value;
    }

    //购物车是否存在
    protected function hasCid($value, $rule, $data = [], $name = '') {
         $data = loadOnly('Cart')->order4store($value);
         $list = $data['list'];
         $arr = [];
         foreach($list as $k => $v) {
            $arr[$v['id']] = true;
         }
         $ids = $value;
         if(is_string($ids)) {
            $ids = explode(',', $ids);
         }
         foreach ($ids as $k => $id) {
             if(!isset($arr[$id])) {
                $msg = '购物车ID不存在';
                if(isset($this->message[$name . '.has'])) {
                    $msg = $this->message[$name . '.has'];
                }
                return $id . '.' . $msg;
             }
         }
         return true;
    }

    //目前只支持同时购买一家店的商品
    protected function storesNum($value, $rule, $data = []) {
        $data = loadOnly('Cart')->order4store($value);
        return count($data['sids']) == 1;
    }

    //验证购物车购买商品的店铺是否开业
    protected function stores($value, $rule, $data = []) {
        $data = loadOnly('Cart')->order4store($value);
        $sids = $data['sids'];
        $statusEnum = loadEnum('StoreStatus');
        foreach($sids as $sid => $row) {
            if(empty($row)) {
                return $sid . $this->message['cids.stores'];
                break;
            }
            if(!$statusEnum->isShow($row['status'])) {
                return $row['id'] . '.' . $row['name'] . $this->message['cids.stores'];
                break;
            }
        }
        return true;
    }

    //判断商品是否属于店铺
    protected function productsInStroe($value, $rule, $data = []) {
        $data = loadOnly('Cart')->order4store($value);
        $pids  = $data['pids'];
        foreach($pids as $pid => $row) {
            if(empty($row)) {
                return $pid . $this->message['cids.productsInStroe'];
                break;
            }
            if(!isset($data['sids'][$row['sid']])) {
                return $row['id'] . '.' . $row['name'] . $this->message['cids.productsInStroe'];
                break;
            }
        }
        return true;
    }

    //验证购物车购买的商品是否上架
    protected function products($value, $rule, $data = []) {
        $data = loadOnly('Cart')->order4store($value);
        $pids  = $data['pids'];
        $statusEnum = loadEnum('ProductStatus');
        foreach($pids as $pid => $row) {
            if(empty($row)) {
                return $pid . $this->message['cids.products'];
                break;
            }
            if(!$statusEnum->isShow($row['status'])) {
                return $row['id'] . '.' . $row['name'] . $this->message['cids.products'];
                break;
            }
        }
        return true;
    }

    //验证规格库存是否足够
    protected function productSpecs($value, $rule, $data = []) {
        $data = loadOnly('Cart')->order4store($value);
        $psids = $data['psids'];
        $list = $data['list'];
        $nexusModel = loadModel('tysj\\ProductSpecsNexus');
        foreach($list as $k => $v) {
            $row = $psids[$v['psid']];
            if(empty($row)) {
                return $v['psid'] . $this->message['cids.productSpecs.nexus'];
            }
            $count = $nexusModel->where(['pid' => $v['pid'], 'psid' => $v['psid']])->count();
            if($count == 0) {
                return $row['id'] . '.' . $row['name'] . $this->message['cids.productSpecs.nexus'];
            }
            if($row['inventory'] < $v['num']) {
                return $row['id'] . '.' . $row['name'] . $this->message['cids.productSpecs.num'];
            }
            if($row['min_purchase_quantity'] > $v['num']) {
                return $row['id'] . '.' . $row['name'] . $this->message['cids.productSpecs.minBuy'];
            }
            return true;
        }
        return true;
    }

    //验证是否可以修改地址
    protected function isSetAddress($value, $rule, $data = []) {
        $statusEnum = loadEnum('OrderStatus');
        $order = loadOnly('Model')->find('jy\\Order', $data['id']);
        if(empty($order)) {
            return false;
        }
        return $order['status'] == $statusEnum->code2key('daifahuo') || $order['status'] == $statusEnum->code2key('daizhifu');
    }

    //验证是否是待发货状态
    protected function sendStatus($value, $rule, $data = []) {
        $statusEnum = loadEnum('OrderStatus');
        $order = loadOnly('Model')->find('jy\\Order', $data['id']);
        if(empty($order)) {
            return false;
        }
        return $order['status'] == $statusEnum->code2key('daifahuo');
    }

    //验证是否是当前店铺的订单
    protected function isStoreOrder($value, $rule, $data = []) {
        $store = loadOnly('tysj\\Store')->current_store();
        if(empty($store)) {
            return false;
        }
        $order = loadOnly('Model')->find('jy\\Order', $data['id']);
        if(empty($order)) {
            return false;
        }
        return $order['sid'] == $store['id'];
    }

    //验证是否可以收获
    protected function harvest($value, $rule, $data = []) {
        $statusEnum = loadEnum('OrderStatus');
        $order = loadOnly('Model')->find('jy\\Order', $data['id']);
        return $order['status'] == $statusEnum->code2key('daishouhuo');
    }

    //验证是否可以收获
    protected function reverse($value, $rule, $data = []) {
        $statusEnum = loadEnum('OrderStatus');
        $order = loadOnly('Model')->find('jy\\Order', $data['id']);
        if(empty($order)) {
            return false;
        }
        return $order['status'] == $statusEnum->code2key('daizhifu');
    }

    //订单是否可以退款
    protected function isRefund($value, $rule, $data = []) {
        $statusEnum = loadEnum('OrderStatus');
        $order = loadOnly('Model')->find('jy\\Order', $data['id']);
        return $statusEnum->isRefund($order['status']);
    }

    //订单退款金额是否小于等于可退款金额
    protected function fee($value, $rule, $data = []) {
        $order = loadOnly('Model')->find('jy\\Order', $data['id']);
        return $order['total_fee'] - $order['refund_fee'] >= $value;
    }

    //推广用户信息验证
    protected function spreadid($value, $rule, $data = []) {
        if(empty($value) || $value == '') {
            return true;
        }
        return $this->has($value, 'tyyh\\User', $data);
    }

    //允许aid为空的特殊情况
    protected function aid_require($value, $rule, $data = []) {
        return isset($data['take_type']) && $data['take_type'] == loadEnum('TakeType')->code2key('ziti');
    }

    //判断是否有足够的余额
    protected function excess($value, $rule, $data = []) {
        $wallet = loadOnly('tyyh\\UserWallet')->get_user_wallet($data['uid']);
        return $wallet['balance'] >= $data['balance'];
    }
}
